<template>
    <div class="my-scroll" ref="scroller">
        <section class="scroll-inner">
            <div class="scroll-header" v-if="downFlag">
                上拉刷新
            </div>
            <slot></slot>
            <div class="scroll-fooer" v-if="flag">
                正在加载
            </div>
        </section>
    </div>
</template>
<script>
    import iScroll from 'iscroll/build/iscroll-probe' ;

    export default {
        props: {
            //滚动时的回调
            onScroll:{
                type:Function,
                default:()=>{}
            },
            //加载更多回调
            onloadMore:{
                type:Function,
                default:()=>{}
            },
            //距底部多少像素触发onloadMore
            onEndReachedThreshold:{
                type:Number,
                default:40
            },
            onTopReachedThreshold:{
                type:Number,
                default:40
            },
            //该函数用于组件初始化的时候在外部接收主件内部的iScroll对象
            scroll:{
                type:Function,
                default:()=>{}
            },
            onrefresh:{
                type : Function ,
                default :() => {}
            },
            //speed 为1、2、3
            speed:{
                type:Number,
                default:3
            }
        },

        data() {
            return {
                //事件
                timeOut:[],
                cacheY:0,
                el:null,
                flag:false ,
                downFlag:false
            }
        },

        beforeMount(){
            this._touchmove = this._touchmove.bind(this);
            this._refresh = this._refresh.bind(this);
        },

        mounted() {

            this.el = this.$refs.scroller;

            this.iScroll = new iScroll(this.el, {
                mouseWheel: true,
                probeType: ~~this.speed,  // 调节在scroll事件触发中探针的活跃度或者频率
                scrollbars: "custom",
                fadeScrollbars: true,
                disablePointer: true,
                disableTouch: false,
                disableMouse: false,
                momentum: true,
                click: true//this._iScrollClick()
            });

            this.scroll(this.iScroll);

            this.bindScrollEvent();
            document.addEventListener(`touchmove`,this._touchmove,false);
            //监听窗口变化，刷新iscorll
            window.addEventListener(`resize`,this._refresh,false);

        },

        beforeDestroy(){
            this.iScroll.destroy();
            this.timeOut.forEach(t=>clearTimeout(t));
            document.removeEventListener(`touchmove`,this._touchmove,false);
            window.removeEventListener(`resize`,this._refresh,false);
        },

        methods: {
            //差值计算

            getDiff() {
                const {
                    y,
                    maxScrollY
                } = this.iScroll;
                if (y > 0 || Math.abs(y) > Math.abs(maxScrollY)) return false;
                return Math.abs(maxScrollY) - Math.abs(y);
            },

            bindScrollEvent() {

                this.iScroll.on(`beforeScrollStart`,()=>{
                    const diff = this.getDiff();
                    if (diff !== false) {
                        this.cacheY = diff;
                        this.shouldRefresh();
                    };
                });

                this.iScroll.on(`scroll`,this.scrollEvent.bind(this));

                this.iScroll.on(`scrollEnd`, this.scrollEvent.bind(this));

            },

            scrollEvent(){
                this.shouldRefresh();
                const diff = this.getDiff();
                if (diff === false) return;
                if ( Math.abs(diff - this.cacheY) >= 2) {

                    let direction = diff - this.cacheY > 0 ? 'down' : 'up';

                    this.onScroll({
                        scroller: this.iScroll,
                        direction: direction
                    });

                    if (!this.flag && direction === 'up' && diff < this.onEndReachedThreshold) {
                        this.onloadMore();
                        this.flag = true;
                    } 
                    else if(!this.downFlag && direction === 'down'){
                        this.downFlag = true
                    }
                    else {
                        if (diff > this.onEndReachedThreshold) {
                            this.flag = false;
                        }
                    }

                    this.cacheY = diff;
                }

            },

            shouldRefresh(){
                const {
                    scroller,
                    wrapperHeight,
                    scrollerHeight
                } = this.iScroll;

                const { clientHeight } = scroller;

                let refresh = false;

                if (this.el && this.el.clientHeight !== wrapperHeight) {
                    refresh = true;
                }

                if (clientHeight !== scrollerHeight || refresh) {
                    this._refresh();
                }
            },

            _refresh() {
                this.iScroll && this.timeOut.push(
                    setTimeout(() => this.iScroll.refresh(), 10)
                );
            },

            _touchmove (e) {
                // e.preventDefault();
            },

            _iScrollClick() {
                const userAgent = navigator.userAgent;
                if (/iPhone|iPad|iPod|Macintosh/i.test(userAgent)) return false;
                if (/Chrome/i.test(userAgent)) return (/Android/i.test(userAgent));
                if (/Silk/i.test(userAgent)) return false;
                if (/Android/i.test(userAgent)) {
                    var s = userAgent.substr(userAgent.indexOf('Android') + 8, 3);
                    return parseFloat(s[0] + s[3]) < 44 ? false : true;
                }
            }
        }
    }
</script>
<style scoped lang="scss">
    .my-scroll {
        height: 100%;
        width: 100%;
        overflow: hidden;
        position: relative;
        .scroll-inner {
            width: 100%;
        }
    }
    .scroll-fooer{
        background: red;
        padding: 0.8rem;
    }
</style>

<style lang="scss">
    .iScrollVerticalScrollbar{
        position: absolute;
        z-index: 20;
        width: 3px;
        bottom: 2px;
        top: 2px;
        right: 0;

        .iScrollIndicator{
            background: rgba(0,0,0,.5);
            border-radius: 4px;
        }
    }
</style>


